﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO.Ports;
using System.Runtime.Serialization;
using System.Xml.Serialization;
using AMStudio.Log;

namespace AMStudio.Common
{
    [Serializable]
    public class TraceConfig : DeviceConfig
    {
        private string pathName = string.Empty;
        public string PathName
        {
            get { return pathName; }
            set { pathName = value; }
        }
        private string stationNo = string.Empty;
        public string StationNo
        {
            get { return stationNo; }
            set { stationNo = value; }
        }
        private bool consoleEnable = false;
        public bool ConsoleEnable
        {
            get { return consoleEnable; }
            set { consoleEnable = value; }
        }
    }

    [Serializable]
    public class MachineConfig
    {
        private static MachineConfig defaultConfig=null;
        public static MachineConfig Default
        {
            get
            {
                if (defaultConfig == null)
                {
                    SimpleConfigProvider<MachineConfig> myConfigProvider = new SimpleConfigProvider<MachineConfig>(@"Config\Machine\MachineConfig.xml");
                    defaultConfig = myConfigProvider.GetConfig();
                    myConfigProvider.SaveConfig(defaultConfig);
                    defaultConfig.St11Scanner.XMLInterpreter(new StreamingContext());
                    defaultConfig.St1Scanner.XMLInterpreter(new StreamingContext());
                    defaultConfig.St1ScannerReject.XMLInterpreter(new StreamingContext());
                    defaultConfig.St1Printer.XMLInterpreter(new StreamingContext());
                }
                return defaultConfig;           
            }
        }

        public string[] Devices = new string[] { "DialTable PLC",
            "Oven PLC", "St1 Housing Scanner", "St1 Reject Scanner", "St11 Scanner","St10 Laser"};
        public OmronPLCConfig DialTablePLC = new OmronPLCConfig();
        public OmronPLCConfig OvenPLC = new OmronPLCConfig();
        public ScannerConfig St1Scanner = new ScannerConfig();
        public ScannerConfig St1ScannerReject = new ScannerConfig();
        public ScannerConfig St11Scanner = new ScannerConfig();
        public LaserConfig St10Laser = new LaserConfig();
        public PrinterConfig St1Printer = new PrinterConfig();
        public TraceConfig St12Trace = new TraceConfig();
    }
    
    [Serializable]
    public class DeviceConfig
    {
        private string hardwareName = string.Empty;
        public string HardwareName
        {
            get { return hardwareName; }
            set { hardwareName = value; }
        }

        private string hardwareEvent = string.Empty;
        public string HardwareEvent
        {
            get { return hardwareEvent; }
            set { hardwareEvent = value; }
        }
    }

    [Serializable]
    public class LaserConfig:DeviceConfig
    {
        private string iPAddress = string.Empty;
        public string IPAddress
        {
            get { return iPAddress; }
            set { iPAddress = value; }
        }

        private int tcpPort;
        public int TcpPort
        {
            get { return tcpPort; }
            set { tcpPort = value; }
        }
    }
    
    [Serializable]
    public class ScannerConfig:DeviceConfig
    {
        public SerialPortConfig SerialPort = new SerialPortConfig("COM7", "115200,N,8,1", "\\r\\n", Handshake.None);

        private string activeCode = "!";

        public string ActiveCode
        {
            get { return activeCode; }
            set { activeCode = value; }
        }
        private string deactiveCode = "#";

        public string DeactiveCode
        {
            get { return deactiveCode; }
            set { deactiveCode = value; }
        }

        public void XMLInterpreter(StreamingContext context)
        {
            SerialPort.XMLInterpreter(context);
        }

    }

    [Serializable]
    public class PrinterConfig : DeviceConfig
    {
        public SerialPortConfig SerialPort = new SerialPortConfig("COM7", "115200,N,8,1", "\\r\\n", Handshake.None);

        private string templetFileName = "1";
        public string TempletFileName
        {
            get { return templetFileName; }
            set { templetFileName = value; }
        }
        private string barcodeTemplet = "1";
        public string BarcodeTemplet
        {
            get { return barcodeTemplet; }
            set { barcodeTemplet = value; }
        }
        private string textTemplet = "1";
        public string TextTemplet
        {
            get { return textTemplet; }
            set { textTemplet = value; }
        }
        private string parameters1Templet = "1";
        public string Parameters1Templet
        {
            get { return parameters1Templet; }
            set { parameters1Templet = value; }
        }
        private string parameters2Templet = "1";
        public string Parameters2Templet
        {
            get { return parameters2Templet; }
            set { parameters2Templet = value; }
        }

        private string printerModule = "GK888t";

        public string PrinterModule
        {
            get { return printerModule; }
            set { printerModule = value; }
        }
        public void XMLInterpreter(StreamingContext context)
        {
            SerialPort.XMLInterpreter(context);
        }

    }

    [Serializable]
    public class OmronPLCConfig:DeviceConfig
    {
        private int address;
        public int Address
        {
            get { return address; }
            set { address = value; }
        }

        private int commTimeout;
        public int CommTimeout
        {
            get { return commTimeout; }
            set { commTimeout = value; }
        }

        private int nodeAddress;
        public int NodeAddress
        {
            get { return nodeAddress; }
            set { nodeAddress = value; }
        }

        private int unitAddress;
        public int UnitAddress
        {
            get { return unitAddress; }
            set { unitAddress = value; }
        }

        private string iPAddress = string.Empty;
        public string IPAddress
        {
            get { return iPAddress; }
            set { iPAddress = value; }
        }

        private int tcpPort;
        public int TcpPort
        {
            get { return tcpPort; }
            set { tcpPort = value; }
        }
    }

    [Serializable]
    public class SerialPortConfig
    {
        public bool Enabled = true;
        public string PortName = "COM1";
        public string Paramters = "9600,N,8,1";
        [XmlIgnore]
        public int BandRate = 9600;
        [XmlIgnore]
        public System.IO.Ports.Parity Parity = System.IO.Ports.Parity.None;
        [XmlIgnore]
        public int DataBits = 8;
        [XmlIgnore]
        public System.IO.Ports.StopBits StopBits = System.IO.Ports.StopBits.One;

        public System.IO.Ports.Handshake HandShake = System.IO.Ports.Handshake.None;
        public int ReadTimeout = 1000;
        public int WriteTimeout = 1000;

        /// <summary>
        /// please pay attention on \\r==\r, \\n=\n
        /// </summary>
        public string ETX = "\\r\\n";

        //[OnDeserialized]
        public void XMLInterpreter(StreamingContext context)
        {
            try
            {
                string[] paras = Paramters.Split(new char[] { ',' });
                BandRate = int.Parse(paras[0]);
                switch (paras[1].ToUpper())
                {
                    case "N":
                        this.Parity = System.IO.Ports.Parity.None;
                        break;
                    case "E":
                        this.Parity = System.IO.Ports.Parity.Even;
                        break;
                    case "O":
                        this.Parity = System.IO.Ports.Parity.Odd;
                        break;
                    case "S":
                        this.Parity = System.IO.Ports.Parity.Space;
                        break;
                    case "M":
                        this.Parity = System.IO.Ports.Parity.Mark;
                        break;
                    default:
                        throw new Exception();
                }
                this.DataBits = int.Parse(paras[2]);
                switch (paras[3])
                {
                    case "1":
                        this.StopBits = System.IO.Ports.StopBits.One;
                        break;
                    case "1.5":
                        this.StopBits = System.IO.Ports.StopBits.OnePointFive;
                        break;
                    case "2":
                        this.StopBits = System.IO.Ports.StopBits.Two;
                        break;
                    case "0":
                        this.StopBits = System.IO.Ports.StopBits.None;
                        break;
                    default:
                        throw new Exception();
                }
                ETX = ETX.Replace("\\r", "\r").Replace("\\n", "\n");
            }
            catch
            {
                throw new Exception("Wrong config file,'" + this.Paramters + "' com parameters format wrong");
            }
        }

        public SerialPortConfig()
        {
        }

        public SerialPortConfig(string portName, string parameters)
            : this(portName, parameters, System.IO.Ports.Handshake.None, 1000, 1000)
        {

        }
        public SerialPortConfig(string portName, string parameters, string etx, System.IO.Ports.Handshake handShake)
            : this(portName, parameters, System.IO.Ports.Handshake.None, 1000, 1000, etx)
        {
            this.HandShake = handShake;
        }
        public SerialPortConfig(string portName, string parameters, string etx)
            : this(portName, parameters, System.IO.Ports.Handshake.None, 1000, 1000, etx)
        {

        }
        public SerialPortConfig(string portName, string parameters, System.IO.Ports.Handshake handShake, int readTimeout, int writeTimeout)
        {
            this.PortName = portName;
            this.Paramters = parameters;
            this.HandShake = handShake;
            this.ReadTimeout = readTimeout;
            this.WriteTimeout = writeTimeout;
            //this.XMLInterpreter(new StreamingContext());
        }
        public SerialPortConfig(string portName, string parameters, System.IO.Ports.Handshake handShake, int readTimeout, int writeTimeout, string etx)
        {
            this.PortName = portName;
            this.Paramters = parameters;
            this.HandShake = handShake;
            this.ReadTimeout = readTimeout;
            this.WriteTimeout = writeTimeout;
            this.ETX = etx;
            //this.XMLInterpreter(new StreamingContext());
        }
        //
        // 摘要:
        //     使用指定的端口名称、波特率、奇偶校验位、数据位和停止位初始化 System.IO.Ports.SerialPort 类的新实例。
        //
        // 参数:
        //   baudRate:
        //     波特率。
        //
        //   portName:
        //     要使用的端口（例如 COM1）。
        //
        //   dataBits:
        //     数据位值。
        //
        //   parity:
        //     System.IO.Ports.SerialPort.Parity 值之一。
        //
        //   stopBits:
        //     System.IO.Ports.SerialPort.StopBits 值之一。
        public SerialPortConfig(string portName, int baudRate, System.IO.Ports.Parity parity, int dataBits, System.IO.Ports.StopBits stopBits)
            : this(portName, baudRate, parity, dataBits, stopBits, System.IO.Ports.Handshake.None)
        {
        }
        //
        // 摘要:
        //     使用指定的端口名称、波特率、奇偶校验位、数据位和停止位初始化 System.IO.Ports.SerialPort 类的新实例。
        //
        // 参数:
        //   baudRate:
        //     波特率。
        //
        //   portName:
        //     要使用的端口（例如 COM1）。
        //
        //   dataBits:
        //     数据位值。
        //
        //   parity:
        //     System.IO.Ports.SerialPort.Parity 值之一。
        //
        //   stopBits:
        //     System.IO.Ports.SerialPort.StopBits 值之一。
        public SerialPortConfig(string portName, int baudRate, System.IO.Ports.Parity parity, int dataBits, System.IO.Ports.StopBits stopBits, System.IO.Ports.Handshake handShake)
        {
            this.PortName = portName;
            this.BandRate = baudRate;
            this.Parity = parity;
            this.DataBits = dataBits;
            this.StopBits = stopBits;
            this.HandShake = handShake;
        }

    }
}
